#include <string.h>
#include "esp_lvgl_port.h"
#include "esp_log.h"
#include "bilibili_ui.h"
#include "main_ui.h"
#include "ui_setting.h"
#include "md_images.h"
#include "func_pin_image.h"
#include "md_languages.h"
#include "wifi_main.h"
#include "esp_wifi.h"
#include "esp_http_client.h"
#include "esp_crt_bundle.h"
#include "cJSON.h"

#define BILIBILI_ACCOUNT_NAME   "米多s"
#define BILIBILI_ACCOUNT_NUMBER "3546974299097449"
static const char *TAG = "bilibili_ui"; // 日志标签

// 声明字体
LV_FONT_DECLARE(myFont);
LV_FONT_DECLARE(lv_font_montserrat_14);

static int g_fans_prvs = 0; // 存储上一次的粉丝数量，用于比较粉丝数变化
static lv_obj_t *ui_LabelFansCount;
// 声明动画变量
static lv_anim_t anim_label1, anim_label2, anim_label3, anim_label4, anim_label5;
static TaskHandle_t s_bilibili_get_task = NULL;

void flow1_Animation(lv_obj_t *TargetObject, int delay);
void flow2_Animation(lv_obj_t *TargetObject, int delay);
void flow3_Animation(lv_obj_t *TargetObject, int delay);
void flow4_Animation(lv_obj_t *TargetObject, int delay);
void flow5_Animation(lv_obj_t *TargetObject, int delay);
void _ui_anim_callback_set_x(lv_anim_t *a, int32_t v);

void exit_bilibili_ui(lv_obj_t *root)
{
    // 停止所有动画
    lv_anim_del(&anim_label1, NULL);
    lv_anim_del(&anim_label2, NULL);
    lv_anim_del(&anim_label3, NULL);
    lv_anim_del(&anim_label4, NULL);
    lv_anim_del(&anim_label5, NULL);
    // 停止所有动画
    lv_anim_del(NULL, _ui_anim_callback_set_x); // 删除所有使用此回调的动画
    switch_to_main_screen();                    // 切换到主界面
    lv_obj_del(root);
    if (s_bilibili_get_task) {
        vTaskDelete(s_bilibili_get_task);
        s_bilibili_get_task = NULL;
    }
}

// 手势事件回调
static void event_handler(lv_event_t *e)
{
    lv_event_code_t code = lv_event_get_code(e);

    if (code == LV_EVENT_GESTURE) {
        lv_indev_t *indev = lv_indev_get_act();
        if (!indev)
            return;

        lv_dir_t dir = lv_indev_get_gesture_dir(indev);
        // 右划或上划退出
        if (dir == LV_DIR_RIGHT || dir == LV_DIR_TOP) {
            lv_obj_t *root = lv_event_get_target(e);
            exit_bilibili_ui(root);
        }
    }
}

/**
 * @brief 获取B站指定用户的粉丝数
 * @param uid 用户ID字符串
 * @return 返回包含JSON响应数据的字符串指针，需要调用者释放内存；失败返回NULL
 */
static char *app_wifi_get_bilibili_fans(const char *uid)
{
    char *url = NULL;
    char *result = NULL;
    // 动态构建API请求URL
    asprintf(&url, "https://api.bilibili.com/x/relation/stat?vmid=%s", uid);
    ESP_ERROR_CHECK_WITHOUT_ABORT(url == NULL); // 检查URL是否生成成功
    // 配置HTTP客户端参数
    esp_http_client_config_t config = {
        .url = url,
        .method = HTTP_METHOD_GET,
        .timeout_ms = 60000,
        .disable_auto_redirect = false,             // 启用自动重定向
        .crt_bundle_attach = esp_crt_bundle_attach, // 启用TLS验证
    };

    // 初始化HTTP客户端
    esp_http_client_handle_t client = esp_http_client_init(&config);

    // 打开HTTP连接
    esp_err_t err = esp_http_client_open(client, 0);
    // 获取响应头内容长度
    int content_length = esp_http_client_fetch_headers(client);
    // 检查是否为分块传输编码
    if (esp_http_client_is_chunked_response(client)) {
        esp_http_client_get_chunk_length(client, &content_length);
    }
    ESP_LOGD(TAG, "content_length=%d", content_length);
    if (content_length < 0) {
        ESP_LOGE(TAG, "HTTP client fetch headers failed!");
        goto end; // 跳转到清理环节
    }
    // 分配内存存储响应内容
    result = (char *)malloc(content_length + 1);
    // 读取响应数据
    int read = esp_http_client_read_response(client, result, content_length);
    if (read != content_length) {
        ESP_LOGE(TAG, "HTTP_ERROR: read=%d, length=%d", read, content_length);
        free(result);
        result = NULL;
    } else {
        result[content_length] = 0; // 添加字符串结束符
        ESP_LOGD(TAG, "result: %s, size: %d", result, strlen(result));
    }

end:
    // 清理资源
    free(url);
    esp_http_client_close(client);
    esp_http_client_cleanup(client);
    return result != NULL ? result : NULL;
}

/**
 * @brief 解析JSON数据提取粉丝数量
 * @param json_data 包含JSON数据的字符串
 * @return 成功返回粉丝数量，失败返回NULL
 */
static int cJSON_parse_follower(const char *json_data)
{
    // 解析JSON字符串
    cJSON *root = cJSON_Parse(json_data);
    if (root == NULL) {
        printf("Error parsing JSON data.\n");
        return NULL;
    }

    /*
    {"code":0,"message":"0","ttl":1,"data":{"mid":1301874808,"following":29,"whisper":0,"black":0,"follower":0}}
*/
    // 获取"data"对象
    cJSON *data = cJSON_GetObjectItem(root, "data");
    if (data != NULL) {
        // 获取"follower"字段
        cJSON *follower = cJSON_GetObjectItem(data, "follower");
        if (follower != NULL) {
            cJSON_Delete(root);        // 释放JSON对象内存
            return follower->valueint; // 返回粉丝数量整数值
        } else {
            printf("Error extracting 'follower' parameter.\n");
        }
    } else {
        printf("Error extracting 'data' object.\n");
    }
    cJSON_Delete(root); // 释放JSON对象内存
    return NULL;
}

/*
    {"code":0,"message":"0","ttl":1,"data":{"mid":1301874808,"following":29,"whisper":0,"black":0,"follower":0}}
*/
/**
 * @brief HTTP获取任务，定期查询B站粉丝数量并更新UI
 * @param pvParameters FreeRTOS任务参数（未使用）
 */
static void http_get_task(void *pvParameters)
{
    wifi_init();
    // 等待 WiFi 连接成功
    EventBits_t bits = xEventGroupWaitBits(s_wifi_event_group,
                                           WIFI_CONNECTED_BIT,
                                           pdFALSE,               // 不清除位
                                           pdFALSE,               // 不等待所有位
                                           pdMS_TO_TICKS(30000)); // 等待30秒
    if (bits & WIFI_CONNECTED_BIT) {
        char *text = NULL;
        while (1) {
            // 获取B站粉丝数据
            const char *result = app_wifi_get_bilibili_fans(BILIBILI_ACCOUNT_NUMBER);
            if (result != NULL) {
                //ESP_LOGI(TAG, "HTTP GET result: %s", result);
                // 解析粉丝数量
                int fans = cJSON_parse_follower(result);
                //ESP_LOGI(TAG, "Bilibili fans: %d", fans);
                // 动态生成显示文本
                asprintf(&text, "祝贺您获得 %d 粉丝", fans);
                // 更新LVGL标签文本
                lv_label_set_text(ui_LabelFansCount, text);
                free(text);
                // 检查粉丝数是否增加
                if (fans > g_fans_prvs) {
                    //
                }

                g_fans_prvs = fans; // 更新上一次粉丝数量
            } else {
                ESP_LOGE(TAG, "HTTP GET failed!");
            }
            /* 每2秒刷新一次 */
            vTaskDelay(2000 / portTICK_PERIOD_MS);
        }
    }
    vTaskDelete(NULL);
}

/* 
 * @brief:创建空调控制界面
 */
lv_obj_t *create_bilibili_ui(void)
{
    lv_obj_t *root = lv_obj_create(NULL);
    if (!root)
        return NULL;

    lv_obj_set_size(root, LV_PCT(100), LV_PCT(100));
    uint32_t color = get_screen_color_val();
    lv_obj_set_style_bg_color(root, lv_color_hex(color), 0);
    lv_obj_clear_flag(root, LV_OBJ_FLAG_SCROLLABLE);
    // 设置屏幕背景不透明度为255（完全不透明）
    lv_obj_set_style_bg_opa(root, 255, LV_PART_MAIN | LV_STATE_DEFAULT);
    // 使根对象可点击以接收手势事件
    lv_obj_add_flag(root, LV_OBJ_FLAG_CLICKABLE);
    lv_obj_add_event_cb(root, event_handler, LV_EVENT_GESTURE, root);

    // 创建用户名称标签
    lv_obj_t *ui_LabelUserName = lv_label_create(root);
    // 设置标签宽度为自适应内容
    lv_obj_set_width(ui_LabelUserName, LV_SIZE_CONTENT);
    // 设置标签高度为自适应内容
    lv_obj_set_height(ui_LabelUserName, LV_SIZE_CONTENT);
    // 设置X坐标（水平位置）
    lv_obj_set_x(ui_LabelUserName, 0);
    // 设置Y坐标（垂直位置）
    lv_obj_set_y(ui_LabelUserName, 9);
    // 设置对齐方式为居中
    lv_obj_set_align(ui_LabelUserName, LV_ALIGN_CENTER);
    // 设置标签文本内容（从配置中获取B站账户名称）
    lv_label_set_text(ui_LabelUserName, BILIBILI_ACCOUNT_NAME);
    // 设置文本颜色为白色
    lv_obj_set_style_text_color(ui_LabelUserName, lv_color_hex(0xFFFFFF), LV_PART_MAIN | LV_STATE_DEFAULT);
    // 设置文本不透明度为255（完全不透明）
    lv_obj_set_style_text_opa(ui_LabelUserName, 255, LV_PART_MAIN | LV_STATE_DEFAULT);
    // 设置文本字体为myFont
    lv_obj_set_style_text_font(ui_LabelUserName, &myFont, LV_PART_MAIN | LV_STATE_DEFAULT);

    // 创建粉丝数量标签
    ui_LabelFansCount = lv_label_create(root);
    lv_obj_set_width(ui_LabelFansCount, LV_SIZE_CONTENT);
    lv_obj_set_height(ui_LabelFansCount, LV_SIZE_CONTENT);
    lv_obj_set_x(ui_LabelFansCount, 0);
    lv_obj_set_y(ui_LabelFansCount, 42);
    lv_obj_set_align(ui_LabelFansCount, LV_ALIGN_CENTER);
    // 设置初始粉丝数量文本
    lv_label_set_text(ui_LabelFansCount, "祝贺您获得 0 粉丝");
    lv_obj_set_style_text_color(ui_LabelFansCount, lv_color_hex(0xFFFFFF), LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_opa(ui_LabelFansCount, 255, LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_font(ui_LabelFansCount, &myFont, LV_PART_MAIN | LV_STATE_DEFAULT);

    // 创建标签1（显示"恭喜你发现镇站之宝"）
    lv_obj_t *ui_Label1 = lv_label_create(root);
    lv_obj_set_width(ui_Label1, LV_SIZE_CONTENT);
    lv_obj_set_height(ui_Label1, LV_SIZE_CONTENT);
    lv_obj_set_x(ui_Label1, -43); // 相对于中心位置向左偏移43像素
    lv_obj_set_y(ui_Label1, -90); // 相对于中心位置向上偏移90像素
    lv_obj_set_align(ui_Label1, LV_ALIGN_CENTER);
    lv_label_set_text(ui_Label1, "恭喜你发现镇站之宝");
    lv_obj_set_style_text_color(ui_Label1, lv_color_hex(0xFFFFFF), LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_opa(ui_Label1, 255, LV_PART_MAIN | LV_STATE_DEFAULT);
    // 使用较小的字体myFont
    lv_obj_set_style_text_font(ui_Label1, &myFont, LV_PART_MAIN | LV_STATE_DEFAULT);

    // 创建标签2（显示"为 UP 主打 Call"）
    lv_obj_t *ui_Label2 = lv_label_create(root);
    lv_obj_set_width(ui_Label2, LV_SIZE_CONTENT);
    lv_obj_set_height(ui_Label2, LV_SIZE_CONTENT);
    lv_obj_set_x(ui_Label2, -35);
    lv_obj_set_y(ui_Label2, -67);
    lv_obj_set_align(ui_Label2, LV_ALIGN_CENTER);
    lv_label_set_text(ui_Label2, "为 UP 主打 Call");
    lv_obj_set_style_text_color(ui_Label2, lv_color_hex(0xFFFFFF), LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_opa(ui_Label2, 255, LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_font(ui_Label2, &myFont, LV_PART_MAIN | LV_STATE_DEFAULT);

    // 创建标签3（显示"打开了新世界的大门"）
    lv_obj_t *ui_Label3 = lv_label_create(root);
    lv_obj_set_width(ui_Label3, LV_SIZE_CONTENT);
    lv_obj_set_height(ui_Label3, LV_SIZE_CONTENT);
    lv_obj_set_x(ui_Label3, -45);
    lv_obj_set_y(ui_Label3, -46);
    lv_obj_set_align(ui_Label3, LV_ALIGN_CENTER);
    lv_label_set_text(ui_Label3, "打开了新世界的大门");
    lv_obj_set_style_text_color(ui_Label3, lv_color_hex(0xFFFFFF), LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_opa(ui_Label3, 255, LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_font(ui_Label3, &myFont, LV_PART_MAIN | LV_STATE_DEFAULT);

    // 创建标签4（显示"给大佬递茶"）
    lv_obj_t *ui_Label4 = lv_label_create(root);
    lv_obj_set_width(ui_Label4, LV_SIZE_CONTENT);
    lv_obj_set_height(ui_Label4, LV_SIZE_CONTENT);
    lv_obj_set_x(ui_Label4, -15);
    lv_obj_set_y(ui_Label4, -110);
    lv_obj_set_align(ui_Label4, LV_ALIGN_CENTER);
    lv_label_set_text(ui_Label4, "给大佬递茶");
    lv_obj_set_style_text_color(ui_Label4, lv_color_hex(0xFFFFFF), LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_opa(ui_Label4, 255, LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_font(ui_Label4, &myFont, LV_PART_MAIN | LV_STATE_DEFAULT);

    // 创建标签5（显示"我也就看了 3000 遍"）
    lv_obj_t *ui_Label5 = lv_label_create(root);
    lv_obj_set_width(ui_Label5, LV_SIZE_CONTENT);
    lv_obj_set_height(ui_Label5, LV_SIZE_CONTENT);
    lv_obj_set_x(ui_Label5, -47);
    lv_obj_set_y(ui_Label5, -20);
    lv_obj_set_align(ui_Label5, LV_ALIGN_CENTER);
    lv_label_set_text(ui_Label5, "我也就看了 3000 遍");
    lv_obj_set_style_text_color(ui_Label5, lv_color_hex(0xFFFFFF), LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_opa(ui_Label5, 255, LV_PART_MAIN | LV_STATE_DEFAULT);
    lv_obj_set_style_text_font(ui_Label5, &myFont, LV_PART_MAIN | LV_STATE_DEFAULT);

    // 创建B站logo图像
    lv_obj_t *ui_Image2 = lv_img_create(root);
    // 设置图像源为预加载的bilibili_png图片
    lv_img_set_src(ui_Image2, get_func_image_data(FUNC_BILIBILI, BILIBILI_LOGO_NUM));
    lv_obj_set_width(ui_Image2, LV_SIZE_CONTENT);
    lv_obj_set_height(ui_Image2, LV_SIZE_CONTENT);
    lv_obj_set_x(ui_Image2, 0);
    lv_obj_set_y(ui_Image2, -64); // 在垂直方向上向上偏移64像素
    lv_obj_set_align(ui_Image2, LV_ALIGN_CENTER);
    // 添加高级点击检测标志，提高点击检测精度
    lv_obj_add_flag(ui_Image2, LV_OBJ_FLAG_ADV_HITTEST);
    // 清除可滚动标志，使图像不可滚动
    lv_obj_clear_flag(ui_Image2, LV_OBJ_FLAG_SCROLLABLE);
    // 设置图像缩放比例为160%（放大图像）
    lv_img_set_zoom(ui_Image2, 160);

    // 创建B站名称图像
    lv_obj_t *ui_Image3 = lv_img_create(root);
    // 设置图像源为预加载的bilibiliname_png图片
    lv_img_set_src(ui_Image3, get_func_image_data(FUNC_BILIBILI, BILIBILI_NAME_NUM));
    lv_obj_set_width(ui_Image3, LV_SIZE_CONTENT);
    lv_obj_set_height(ui_Image3, LV_SIZE_CONTENT);
    lv_obj_set_x(ui_Image3, 0);
    lv_obj_set_y(ui_Image3, 84); // 在垂直方向上向下偏移84像素
    lv_obj_set_align(ui_Image3, LV_ALIGN_CENTER);
    lv_obj_add_flag(ui_Image3, LV_OBJ_FLAG_ADV_HITTEST);
    lv_obj_clear_flag(ui_Image3, LV_OBJ_FLAG_SCROLLABLE);
    // 设置图像缩放比例为180%（放大图像）
    lv_img_set_zoom(ui_Image3, 180);

    // 为各个标签添加动画效果
    flow1_Animation(ui_Label1, 0); // 标签1的流动动画
    flow2_Animation(ui_Label2, 0); // 标签2的流动动画
    flow3_Animation(ui_Label3, 0); // 标签3的流动动画
    flow4_Animation(ui_Label4, 0); // 标签4的流动动画
    flow5_Animation(ui_Label5, 0); // 标签5的流动动画

    // 创建HTTP获取任务
    xTaskCreate(&http_get_task, "http_get_task", 4096, NULL, 5, &s_bilibili_get_task);
    return root;
}

/*****/
/** Describes an animation*/
typedef struct _ui_anim_user_data_t {
    lv_obj_t *target;
    lv_img_dsc_t **imgset;
    int32_t imgset_size;
    int32_t val;
} ui_anim_user_data_t;
void _ui_anim_callback_set_x(lv_anim_t *a, int32_t v)

{
    lv_obj_t *target = (lv_obj_t *)a->var;

    ui_anim_user_data_t *usr = (ui_anim_user_data_t *)a->user_data;
    // 检查目标对象是否有效
    if (usr->target == NULL || lv_obj_is_valid(usr->target) == false) {
        return;
    }
    lv_obj_set_x(usr->target, v);
}
void _ui_anim_callback_free_user_data(lv_anim_t *a)
{
    lv_mem_free(a->user_data);
    a->user_data = NULL;
}
int32_t _ui_anim_callback_get_x(lv_anim_t *a)

{
    ui_anim_user_data_t *usr = (ui_anim_user_data_t *)a->user_data;
    return lv_obj_get_x_aligned(usr->target);
}

void flow1_Animation(lv_obj_t *TargetObject, int delay)
{
    ui_anim_user_data_t *PropertyAnimation_0_user_data = lv_mem_alloc(sizeof(ui_anim_user_data_t));
    PropertyAnimation_0_user_data->target = TargetObject;
    PropertyAnimation_0_user_data->val = -1;

    lv_anim_init(&anim_label1);
    lv_anim_set_time(&anim_label1, 5000);
    lv_anim_set_user_data(&anim_label1, PropertyAnimation_0_user_data);
    lv_anim_set_custom_exec_cb(&anim_label1, _ui_anim_callback_set_x);
    lv_anim_set_values(&anim_label1, -100, 240);
    lv_anim_set_path_cb(&anim_label1, lv_anim_path_linear);
    lv_anim_set_delay(&anim_label1, delay + 0);
    lv_anim_set_deleted_cb(&anim_label1, _ui_anim_callback_free_user_data);
    lv_anim_set_playback_time(&anim_label1, 0);
    lv_anim_set_playback_delay(&anim_label1, 0);
    lv_anim_set_repeat_count(&anim_label1, LV_ANIM_REPEAT_INFINITE);
    lv_anim_set_repeat_delay(&anim_label1, 0);
    lv_anim_set_early_apply(&anim_label1, false);
    lv_anim_set_get_value_cb(&anim_label1, &_ui_anim_callback_get_x);
    lv_anim_start(&anim_label1);
}

void flow2_Animation(lv_obj_t *TargetObject, int delay)
{
    ui_anim_user_data_t *PropertyAnimation_0_user_data = lv_mem_alloc(sizeof(ui_anim_user_data_t));
    PropertyAnimation_0_user_data->target = TargetObject;
    PropertyAnimation_0_user_data->val = -1;

    lv_anim_init(&anim_label2);
    lv_anim_set_time(&anim_label2, 4500);
    lv_anim_set_user_data(&anim_label2, PropertyAnimation_0_user_data);
    lv_anim_set_custom_exec_cb(&anim_label2, _ui_anim_callback_set_x);
    lv_anim_set_values(&anim_label2, -100, 240);
    lv_anim_set_path_cb(&anim_label2, lv_anim_path_linear);
    lv_anim_set_delay(&anim_label2, delay + 0);
    lv_anim_set_deleted_cb(&anim_label2, _ui_anim_callback_free_user_data);
    lv_anim_set_playback_time(&anim_label2, 0);
    lv_anim_set_playback_delay(&anim_label2, 0);
    lv_anim_set_repeat_count(&anim_label2, LV_ANIM_REPEAT_INFINITE);
    lv_anim_set_repeat_delay(&anim_label2, 0);
    lv_anim_set_early_apply(&anim_label2, false);
    lv_anim_set_get_value_cb(&anim_label2, &_ui_anim_callback_get_x);
    lv_anim_start(&anim_label2);
}

void flow3_Animation(lv_obj_t *TargetObject, int delay)
{
    ui_anim_user_data_t *PropertyAnimation_0_user_data = lv_mem_alloc(sizeof(ui_anim_user_data_t));
    PropertyAnimation_0_user_data->target = TargetObject;
    PropertyAnimation_0_user_data->val = -1;

    lv_anim_init(&anim_label3);
    lv_anim_set_time(&anim_label3, 3000);
    lv_anim_set_user_data(&anim_label3, PropertyAnimation_0_user_data);
    lv_anim_set_custom_exec_cb(&anim_label3, _ui_anim_callback_set_x);
    lv_anim_set_values(&anim_label3, -100, 240);
    lv_anim_set_path_cb(&anim_label3, lv_anim_path_linear);
    lv_anim_set_delay(&anim_label3, delay + 0);
    lv_anim_set_deleted_cb(&anim_label3, _ui_anim_callback_free_user_data);
    lv_anim_set_playback_time(&anim_label3, 0);
    lv_anim_set_playback_delay(&anim_label3, 0);
    lv_anim_set_repeat_count(&anim_label3, LV_ANIM_REPEAT_INFINITE);
    lv_anim_set_repeat_delay(&anim_label3, 0);
    lv_anim_set_early_apply(&anim_label3, false);
    lv_anim_set_get_value_cb(&anim_label3, &_ui_anim_callback_get_x);
    lv_anim_start(&anim_label3);
}

void flow4_Animation(lv_obj_t *TargetObject, int delay)
{
    ui_anim_user_data_t *PropertyAnimation_0_user_data = lv_mem_alloc(sizeof(ui_anim_user_data_t));
    PropertyAnimation_0_user_data->target = TargetObject;
    PropertyAnimation_0_user_data->val = -1;

    lv_anim_init(&anim_label4);
    lv_anim_set_time(&anim_label4, 2000);
    lv_anim_set_user_data(&anim_label4, PropertyAnimation_0_user_data);
    lv_anim_set_custom_exec_cb(&anim_label4, _ui_anim_callback_set_x);
    lv_anim_set_values(&anim_label4, -100, 240);
    lv_anim_set_path_cb(&anim_label4, lv_anim_path_linear);
    lv_anim_set_delay(&anim_label4, delay + 0);
    lv_anim_set_deleted_cb(&anim_label4, _ui_anim_callback_free_user_data);
    lv_anim_set_playback_time(&anim_label4, 0);
    lv_anim_set_playback_delay(&anim_label4, 0);
    lv_anim_set_repeat_count(&anim_label4, LV_ANIM_REPEAT_INFINITE);
    lv_anim_set_repeat_delay(&anim_label4, 0);
    lv_anim_set_early_apply(&anim_label4, false);
    lv_anim_set_get_value_cb(&anim_label4, &_ui_anim_callback_get_x);
    lv_anim_start(&anim_label4);
}

void flow5_Animation(lv_obj_t *TargetObject, int delay)
{
    ui_anim_user_data_t *PropertyAnimation_0_user_data = lv_mem_alloc(sizeof(ui_anim_user_data_t));
    PropertyAnimation_0_user_data->target = TargetObject;
    PropertyAnimation_0_user_data->val = -1;

    lv_anim_init(&anim_label5);
    lv_anim_set_time(&anim_label5, 6000);
    lv_anim_set_user_data(&anim_label5, PropertyAnimation_0_user_data);
    lv_anim_set_custom_exec_cb(&anim_label5, _ui_anim_callback_set_x);
    lv_anim_set_values(&anim_label5, -100, 240);
    lv_anim_set_path_cb(&anim_label5, lv_anim_path_linear);
    lv_anim_set_delay(&anim_label5, delay + 0);
    lv_anim_set_deleted_cb(&anim_label5, _ui_anim_callback_free_user_data);
    lv_anim_set_playback_time(&anim_label5, 0);
    lv_anim_set_playback_delay(&anim_label5, 0);
    lv_anim_set_repeat_count(&anim_label5, LV_ANIM_REPEAT_INFINITE);
    lv_anim_set_repeat_delay(&anim_label5, 0);
    lv_anim_set_early_apply(&anim_label5, true);
    lv_anim_set_get_value_cb(&anim_label5, &_ui_anim_callback_get_x);
    lv_anim_start(&anim_label5);
}